﻿using System;
using System.Collections.Generic;
using System.Configuration;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Mail;
using System.Web.Mvc;
using ControleRepresentante.Logic;
using ControleRepresentante.Logic.ImpostoHandlers;
using ControleRepresentante.Logic.Models;
using ControleRepresentante.Logic.Repositories;
using ControleRepresentante.Logic.Repositories.SearchExtensions;
using ControleRepresentante.Logic.Statistics;
using Telerik.Web.Mvc;
using WebSite.Controllers.ControllerExtensions;
using WebSite.Controllers.PrintTemplates;
using WebSite.ViewModels;
using WebSite.ViewModels.DetailsViewModels;
using WebSite.ViewModels.EditViewModels;
using WebSite.ViewModels.IndexViewModels;
using Attribute = ControleRepresentante.Logic.Models.Attribute;

namespace WebSite.Controllers
{
    public class PedidoController : AttributeHolderControllerBase<IPedidoRepository, Pedido, PedidoStatistics>
    {
        private readonly IPrintTemplateSelector m_PrintTemplateSelector;

        public PedidoController(IRepositoryProvider repositoryProvider, ISessionConfiguration sessionConfiguration, IControllerExtensionProvider controllerExtensionProvider, IPrintTemplateSelector printTemplateSelector, IImpostoProvider impostoProvider)
            : base(repositoryProvider, sessionConfiguration, controllerExtensionProvider, impostoProvider)
        {
            m_PrintTemplateSelector = printTemplateSelector;
        }

        protected override Area? Area { get { return ControleRepresentante.Logic.Models.Area.Pedidos; } }

        private Pedido EnsureHasPermissionToPedido(Guid id)
        {
            User user = Repository.User;

            Pedido pedido = Repository.GetModelById(id);

            IEnumerable<Fabrica> fabricaFiltro = user.Filtros.OfType<Fabrica>();
            IEnumerable<Cliente> clienteFiltro = user.Filtros.OfType<Cliente>();
            IEnumerable<Vendedor> vendedorFiltro = user.Filtros.OfType<Vendedor>();
            IEnumerable<Transportadora> transportadoraFiltro = user.Filtros.OfType<Transportadora>();
            if ((fabricaFiltro.Any() && !fabricaFiltro.Any(x => x.Id == pedido.Fabrica.Id)) ||
                (clienteFiltro.Any() && !clienteFiltro.Any(x => x.Id == pedido.Cliente.Id)) ||
                (vendedorFiltro.Any() && !vendedorFiltro.Any(x => x.Id == pedido.Vendedor.Id)) ||
                (transportadoraFiltro.Any() && !transportadoraFiltro.Any(x => x.Id == pedido.Transportadora.Id)))
            {
                throw new RestrictedAreaException();
            }
            return pedido;
        }

        protected override AttributeType AttributeType { get { return AttributeType.Pedido; } }
        
        protected override AttributeHolderDetailsViewModel GetAttributeHolderDetailsViewModel(Pedido model)
        {
            return new PedidoDetailsViewModel(HasPermission(ControleRepresentante.Logic.Models.Area.Clientes, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Vendedores, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Fabricas, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Transportadoras, Operacao.View),
                HasPermission(Operacao.Create),
                HasPermission(Operacao.Print));
        }

        protected override IAttributeHolderIndexViewModel GetAttributeHolderIndexViewModel(PedidoStatistics statistics)
        {
            return new PedidoIndexViewModel(HasPermission(ControleRepresentante.Logic.Models.Area.Clientes, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Vendedores, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Fabricas, Operacao.View),
                HasPermission(ControleRepresentante.Logic.Models.Area.Transportadoras, Operacao.View),
                HasPermission(Operacao.Print), statistics);
        }

        protected override void RegisterIndexColumns(IIndexColumnsProvider indexColumnsProvider)
        {
            base.RegisterIndexColumns(indexColumnsProvider);

            indexColumnsProvider.SetDefaultColumns(
                indexColumnsProvider.RegisterColumn("Data", PedidoIndexColumns.Data),
                indexColumnsProvider.RegisterColumn("Número", PedidoIndexColumns.Numero, true),
                indexColumnsProvider.RegisterColumn("Cliente", PedidoIndexColumns.Cliente),
                indexColumnsProvider.RegisterColumn("Vendedor", PedidoIndexColumns.Vendedor),
                indexColumnsProvider.RegisterColumn("Fábrica", PedidoIndexColumns.Fabrica),
                indexColumnsProvider.RegisterColumn("Transportadora", PedidoIndexColumns.Transportadora),
                indexColumnsProvider.RegisterColumn("Total Mercadoria", PedidoIndexColumns.TotalMercadoria));
            indexColumnsProvider.RegisterColumn("Faturado", PedidoIndexColumns.Faturado);
            indexColumnsProvider.RegisterColumn("Cancelado", PedidoIndexColumns.Cancelado);
            indexColumnsProvider.RegisterColumn("Valor Desconto", PedidoIndexColumns.ValorDesconto);
            indexColumnsProvider.RegisterColumn("Desconto", PedidoIndexColumns.Desconto);
            indexColumnsProvider.RegisterColumn("Condição Pagamento", PedidoIndexColumns.CondicaoPagamento);
            indexColumnsProvider.RegisterColumn("Prazo Entrega", PedidoIndexColumns.PrazoEntrega);
            indexColumnsProvider.RegisterColumn("Observação", PedidoIndexColumns.Observacao);
            indexColumnsProvider.RegisterColumn("Total Peças", PedidoIndexColumns.TotalPecas);
            indexColumnsProvider.RegisterColumn("Criado", PedidoIndexColumns.Criado);
            indexColumnsProvider.RegisterColumn("Modificado", PedidoIndexColumns.Modificado);
        }

        public ActionResult Email()
        {
            Pedido pedido = EnsureHasPermissionToPedido(new Guid("f7f356fa-b692-472f-9c48-84ce44c6d55b"));
            Representante representante = Repository.GetRepresentante();
            IPrintTemplate printTemplate = m_PrintTemplateSelector.GetPrintTemplate(representante, pedido);
            string vendedorPrint = GetVendedorPrint(representante, pedido);
            PedidoPrintViewModel pedidoPrintViewModel = new PedidoPrintViewModel(representante.RepresentanteInfo, pedido, printTemplate.GetNumero(pedido), vendedorPrint);
            string content = GetViewHtml(printTemplate.ViewName, pedidoPrintViewModel);
            SendMail("mteitelbaum@kadimaasset.com.br", "marcteit@gmail.com", "teste", content);
            return new JsonResult{Data = new {Message = "Hello World"}, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
        }

        private string GetViewHtml(string viewName, object model)
        {
            string content;
            ViewEngineResult viewEngineResult = ViewEngines.Engines.FindView(ControllerContext, viewName, null);
            using (StringWriter stringWriter = new StringWriter())
            {
                ViewDataDictionary viewData = new ViewDataDictionary(model);
                ViewContext context = new ViewContext(ControllerContext, viewEngineResult.View, viewData, TempData, stringWriter);
                viewEngineResult.View.Render(context, stringWriter);
                stringWriter.Flush();
                content = stringWriter.ToString();
            }
            return content;
        }

        private static void SendMail(string from, string to, string subject, string content, bool isBodyHtml = true)
        {
            string host = ConfigurationManager.AppSettings["SmtpHost"];
            string user = ConfigurationManager.AppSettings["SmtpUser"];
            string password = ConfigurationManager.AppSettings["SmtpPassword"];
            MailMessage mailMessage = new MailMessage(from, to)
            {
                Body = content,
                IsBodyHtml = isBodyHtml,
                Subject = subject,
            };
            SmtpClient smtpClient = new SmtpClient(host) {Credentials = new NetworkCredential(user, password)};
            smtpClient.Send(mailMessage);
        }

        public ActionResult CreateTargettedPedido(Guid targetId, string targetType)
        {
            ActionResult actionResult = Create(true);
            PedidoEditViewModel pedidoEditViewModel = (PedidoEditViewModel) ((ViewResult)actionResult).Model;
            Pedido pedido = (Pedido) pedidoEditViewModel.Model;
            if (targetType.Contains(typeof (Cliente).ToString().Split('.').Last()))
            {
                pedido.Cliente = RepositoryProvider.GetRepository<IClienteRepository>().GetModelById(targetId);
            }
            else if (targetType.Contains(typeof(Fabrica).ToString().Split('.').Last()))
            {
                pedido.Fabrica = RepositoryProvider.GetRepository<IFabricaRepository>().GetModelById(targetId);
            }
            else if (targetType.Contains(typeof(Transportadora).ToString().Split('.').Last()))
            {
                pedido.Transportadora = RepositoryProvider.GetRepository<ITransportadoraRepository>().GetModelById(targetId);
            }
            else if (targetType.Contains(typeof(Vendedor).ToString().Split('.').Last()))
            {
                pedido.Vendedor = RepositoryProvider.GetRepository<IVendedorRepository>().GetModelById(targetId);
            }
            return actionResult;
        }

        protected override ActionResult Create(bool clearModel)
        {
            List<string> missing = new List<string>();

            IVendedorRepository vendedorRepository = RepositoryProvider.GetRepository<IVendedorRepository>();
            if (vendedorRepository.GetCount() == 0)
            {
                missing.Add("vendedores");
            }

            IClienteRepository clienteRepository = RepositoryProvider.GetRepository<IClienteRepository>();
            if (clienteRepository.GetCount() == 0)
            {
                missing.Add("clientes");
            }

            IFabricaRepository fabricaRepository = RepositoryProvider.GetRepository<IFabricaRepository>();
            if (fabricaRepository.GetCount() == 0)
            {
                missing.Add("fábricas");
            }

            ITransportadoraRepository transportadoraRepository = RepositoryProvider.GetRepository<ITransportadoraRepository>();
            if (transportadoraRepository.GetCount() == 0)
            {
                missing.Add("transportadoras");
            }

            if (missing.Count == 0)
            {
                return base.Create(clearModel);
            }

            string message = String.Format(
                "Pedido não pode ser criado porque não existem {0} cadastrados. Cadastre primeiramente {0}.",
                String.Join(", ", missing.ToArray()));
            
            return View(new PedidoEditViewModel(message));
        }

        protected override AttributeHolderEditViewModel GetEditViewModel()
        {
            Dictionary<Guid, String> clientes = RepositoryProvider.GetRepository<IClienteRepository>().GetModelNames();
            Dictionary<Guid, String> vendedores = RepositoryProvider.GetRepository<IVendedorRepository>().GetModelNames();
            Dictionary<Guid, String> transportadoras = RepositoryProvider.GetRepository<ITransportadoraRepository>().GetModelNames();
            Dictionary<Guid, String> fabricas = RepositoryProvider.GetRepository<IFabricaRepository>().GetModelNames();

            return new PedidoEditViewModel(clientes, vendedores, transportadoras, fabricas);
        }

        public ActionResult Search(int? numero, string vendedorIds, string cliente, string fabricaIds, string transportadoraIds, DateTime? de, DateTime? ate, double? totalMin, double? totalMax, string observacao, bool? faturado, bool? cancelado, int? numeroProdutos, int? numeroPecas, string descricaoProduto, DateTime? criadoDe, DateTime? criadoAte, DateTime? modificadoDe, DateTime? modificadoAte, FormCollection formCollection)
        {
            Dictionary<Attribute, string> attributeMap;
            PedidoStatistics statistics;
            Dictionary<Guid, string> vendedores;
            Dictionary<Guid, string> fabricas;
            Dictionary<Guid, string> transportadoras;

            IEnumerable<Pedido> models = RunSearch(numero, vendedorIds, fabricaIds, transportadoraIds, cliente, de, ate, totalMin, totalMax, observacao, faturado, cancelado, numeroProdutos, numeroPecas, descricaoProduto, criadoDe, criadoAte, modificadoDe, modificadoAte, formCollection, true, out vendedores, out fabricas, out transportadoras, out statistics, out attributeMap);

            return Index(models, statistics, formCollection, x =>
            {
                PedidoIndexViewModel pedidoIndexViewModel = (PedidoIndexViewModel)x;
                pedidoIndexViewModel.VendedorBusca = vendedores;
                pedidoIndexViewModel.FabricaBusca = fabricas;
                pedidoIndexViewModel.TransportadoraBusca = transportadoras;
                SetAttributeSearchValues(pedidoIndexViewModel, attributeMap);
                pedidoIndexViewModel.NumeroBuscaValue = numero;
                pedidoIndexViewModel.VendedorBuscaValue = vendedorIds;
                pedidoIndexViewModel.ClienteBuscaValue = cliente;
                pedidoIndexViewModel.FabricaBuscaValue = fabricaIds;
                pedidoIndexViewModel.TransportadoraBuscaValue = transportadoraIds;
                pedidoIndexViewModel.DeBuscaValue = de;
                pedidoIndexViewModel.AteBuscaValue = ate;
                pedidoIndexViewModel.TotalMinBuscaValue = totalMin;
                pedidoIndexViewModel.TotalMaxBuscaValue = totalMax;
                pedidoIndexViewModel.ObservacaoBuscaValue = observacao;
                pedidoIndexViewModel.FaturadoBuscaValue = faturado;
                pedidoIndexViewModel.CanceladoBuscaValue = cancelado;
                pedidoIndexViewModel.NumeroPecasBuscaValue = numeroPecas;
                pedidoIndexViewModel.NumeroProdutosBuscaValue = numeroProdutos;
                pedidoIndexViewModel.DescricaoProdutoBuscaValue = descricaoProduto;
                pedidoIndexViewModel.CriadoDeBuscaValue = criadoDe;
                pedidoIndexViewModel.CriadoAteBuscaValue = criadoAte;
                pedidoIndexViewModel.ModificadoDeBuscaValue = modificadoDe;
                pedidoIndexViewModel.ModificadoAteBuscaValue = modificadoAte;
            });
        }

        private IEnumerable<Pedido> RunSearch(int? numero, string vendedorIds, string fabricaIds, string transportadoraIds, string cliente, DateTime? de, DateTime? ate, double? totalMin, double? totalMax, string observacao, bool? faturado, bool? cancelado, int? numeroProdutos, int? numeroPecas, string descricaoProduto, DateTime? criadoDe, DateTime? criadoAte, DateTime? modificadoDe, DateTime? modificadoAte, FormCollection formCollection, bool usePaging, out Dictionary<Guid, string> vendedores, out Dictionary<Guid, string> fabricas, out Dictionary<Guid, string> transportadoras, out PedidoStatistics statistics, out Dictionary<Attribute, string> attributeMap)
        {
            EnsureHasPermission(Operacao.View);

            formCollection.Add(Request.QueryString);

            IAttributeRepository attributeRepository = RepositoryProvider.GetRepository<IAttributeRepository>();
            attributeMap = GetAttributeMap(attributeRepository, formCollection);

            vendedores = ParseIds<IVendedorRepository, Vendedor, StatisticsBase>(vendedorIds, x => x.Nome);
            fabricas = ParseIds<IFabricaRepository, Fabrica, StatisticsBase>(fabricaIds, x => x.Nome);
            transportadoras = ParseIds<ITransportadoraRepository, Transportadora, StatisticsBase>(transportadoraIds, x => x.Nome);
            ISearchExtension[] searchExtensions = GetSearchExtensions(formCollection);

            return Repository.GetModels(numero, vendedores.Keys, cliente, fabricas.Keys, transportadoras.Keys, de, ate, totalMin, totalMax, observacao, faturado, cancelado, numeroProdutos, numeroPecas, descricaoProduto, criadoDe, criadoAte, modificadoDe, modificadoAte, attributeMap, searchExtensions, out statistics, usePaging ? GetPage() : -1);
        }

        protected override bool CanPrint { get { return true; } }

        public ActionResult PrintList(int? numero, string vendedorIds, string cliente, string fabricaIds, string transportadoraIds, string de, string ate, double? totalMin, double? totalMax, string observacao, bool? faturado, bool? cancelado, int? numeroProdutos, int? numeroPecas, string descricaoProduto, string criadoDe, string criadoAte, string modificadoDe, string modificadoAte, FormCollection formCollection)
        {
            Dictionary<Attribute, string> attributeMap;
            PedidoStatistics statistics;
            Dictionary<Guid, string> vendedores;
            Dictionary<Guid, string> fabricas;
            Dictionary<Guid, string> transportadoras;

            DateTime date;
            DateTime? deParsed = DateTime.TryParse(de, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;
            DateTime? ateParsed = DateTime.TryParse(ate, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;
            DateTime? criadoDeParsed = DateTime.TryParse(criadoDe, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;
            DateTime? criadoAteParsed = DateTime.TryParse(criadoAte, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;
            DateTime? modificadoDeParsed = DateTime.TryParse(modificadoDe, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;
            DateTime? modificadoAteParsed = DateTime.TryParse(modificadoAte, CultureInfo.GetCultureInfo("pt-br"), DateTimeStyles.None, out date) ? (DateTime?)date : null;

            IEnumerable<Pedido> models = RunSearch(numero, vendedorIds, fabricaIds, transportadoraIds, cliente, deParsed, ateParsed, totalMin, totalMax, observacao, faturado, cancelado, numeroProdutos, numeroPecas, descricaoProduto, criadoDeParsed, criadoAteParsed, modificadoDeParsed, modificadoAteParsed, formCollection, false, out vendedores, out fabricas, out transportadoras, out statistics, out attributeMap);

            return PrintList(models, statistics, formCollection);
        }

        [HttpPost]
        public ActionResult AddPost(Guid id, string comentario)
        {
            EnsureHasPermission(Operacao.View);

            if (!String.IsNullOrWhiteSpace(comentario))
            {
                Post post = new Post
                {
                    Comentario = comentario,
                };
                IUserRepository userRepository = RepositoryProvider.GetRepository<IUserRepository>();
                User user = userRepository.GetModelById(Repository.User.Id);
                post.User = user;
                EnsureHasPermissionToPedido(id).AddPost(post);
                Repository.AddPost(post);
            }
            return RedirectToAction("Details", id);
        }

        [HttpPost]
        public ActionResult Create(Guid clienteId, Guid vendedorId, Guid fabricaId, Guid transportadoraId, DateTime? data, string condicaoPagamento, string prazoEntrega, string observacao, double? desconto, bool faturado, bool cancelado, FormCollection formCollection = null)
        {
            EnsureHasPermission(Operacao.Create);
            if (TryUpdatePedido(clienteId, vendedorId, fabricaId, transportadoraId, data, condicaoPagamento, prazoEntrega, observacao, desconto, faturado, cancelado, formCollection))
            {
                Repository.AddModel(Model);
                Pedido pedido = Model;
                Model = null;
                return RedirectToAction("Details", pedido.Id);
            }
            return Create(false);
        }

        [HttpPost]
        public ActionResult Edit(Guid clienteId, Guid vendedorId, Guid fabricaId, Guid transportadoraId, DateTime? data, string condicaoPagamento, string prazoEntrega, string observacao, double? desconto, bool faturado, bool cancelado, FormCollection formCollection = null)
        {
            EnsureHasPermission(Operacao.Update);
            if (TryUpdatePedido(clienteId, vendedorId, fabricaId, transportadoraId, data, condicaoPagamento, prazoEntrega, observacao, desconto, faturado, cancelado, formCollection))
            {
                Repository.UpdateModel(Model);
                Guid pedidoId = Model.Id;
                Model = null;
                return RedirectToAction("Details", pedidoId);
            }
            return Edit();
        }

        public ActionResult Duplicate(Guid id)
        {
            EnsureHasPermission(Operacao.Create);
            Pedido originalPedido = Repository.GetModelById(id);
            Pedido duplicatedPedido = CreateInstance();
            foreach (AttributeValue attributeValue in originalPedido.AttributeValues)
            {
                duplicatedPedido.AddAttributeValue(new AttributeValue{Attribute = attributeValue.Attribute, Value = attributeValue.Value});
            }
            duplicatedPedido.Cliente = originalPedido.Cliente;
            duplicatedPedido.CondicaoPagamento = originalPedido.CondicaoPagamento;
            duplicatedPedido.Data = DateTime.Today;
            duplicatedPedido.Desconto = originalPedido.Desconto;
            duplicatedPedido.Fabrica = originalPedido.Fabrica;
            duplicatedPedido.Observacao = originalPedido.Observacao;
            duplicatedPedido.PrazoEntrega = originalPedido.PrazoEntrega;
            foreach (Produto produto in originalPedido.Produtos)
            {
                duplicatedPedido.AddProduto(new Produto{Codigo = produto.Codigo, Descricao = produto.Descricao, PrecoUnitario = produto.PrecoUnitario, Quantidade = produto.Quantidade});
            }
            duplicatedPedido.Representante = Repository.GetRepresentante();
            duplicatedPedido.Transportadora = originalPedido.Transportadora;
            duplicatedPedido.Vendedor = originalPedido.Vendedor;

            Model = duplicatedPedido;
            return Edit("Create", true);
        }

        private bool TryUpdatePedido(Guid clienteId, Guid vendedorId, Guid fabricaId, Guid transportadoraId, DateTime? data, string condicaoPagamento, string prazoEntrega, string observacao, double? desconto, bool faturado, bool cancelado, FormCollection formCollection)
        {
            Model.Cliente = RepositoryProvider.GetRepository<IClienteRepository>().GetModelById(clienteId);
            Model.Vendedor = RepositoryProvider.GetRepository<IVendedorRepository>().GetModelById(vendedorId);
            Model.Fabrica = RepositoryProvider.GetRepository<IFabricaRepository>().GetModelById(fabricaId);
            Model.Transportadora = RepositoryProvider.GetRepository<ITransportadoraRepository>().GetModelById(transportadoraId);
            if (data.HasValue)
            {
                Model.Data = data.Value;
            }
            Model.CondicaoPagamento = condicaoPagamento;
            Model.PrazoEntrega = prazoEntrega;
            Model.Observacao = observacao;
            Model.Faturado = faturado;
            Model.Cancelado = cancelado;
            if (desconto.HasValue)
            {
                Model.Desconto = desconto.Value;
            }

            UpdateAttributesToModel(formCollection);

            ModelState.Clear();
            if (!data.HasValue)
            {
                ModelState.AddModelError("Data", "*");
            }
            if (!desconto.HasValue)
            {
                ModelState.AddModelError("Desconto", "*");
            }
            ExtensionsUpdateModel(formCollection);
            return ModelState.IsValid;
        }

        #region Produto

        [GridAction]
        public ActionResult ProdutoSelect()
        {
            return GetView(Model.Produtos);
        }

        [GridAction]
        [HttpPost]
        public ActionResult ProdutoDelete(Guid produtoId)
        {
            Produto produto = Model.Produtos.Single(x => x.Id == produtoId);
            Model.RemoveProduto(produto);
            return GetView(Model.Produtos);
        }

        [GridAction]
        [HttpPost]
        public ActionResult ProdutoInsert(int quantidade, string codigo, string descricao, double precoUnitario)
        {
            Produto produto = new Produto();
            if (TryUpdateProduto(produto, quantidade, codigo, descricao, precoUnitario))
            {
                Model.AddProduto(produto);
            }
            return GetView(Model.Produtos);
        }

        [GridAction]
        [HttpPost]
        public ActionResult ProdutoUpdate(Guid produtoId, int quantidade, string codigo, string descricao, double precoUnitario)
        {
            Produto produto = Model.Produtos.Single(x => x.Id == produtoId);
            TryUpdateProduto(produto, quantidade, codigo, descricao, precoUnitario);
            return GetView(Model.Produtos);
        }

        private ActionResult GetView(IEnumerable<Produto> produtos)
        {
            return View(new GridModel(produtos.Select(x => new ProdutoViewModel(x))));
        }

        private static bool TryUpdateProduto(Produto produto, int quantidade, string codigo, string descricao, double precoUnitario)
        {
            produto.Quantidade = quantidade;
            produto.Codigo = codigo;
            produto.Descricao = descricao;
            produto.PrecoUnitario = precoUnitario;
            return produto.Descricao!= null &&
                   !String.IsNullOrEmpty(produto.Descricao);
        }

        #endregion

        public ActionResult Print(Guid id)
        {
            EnsureHasPermission(Operacao.Print);
            Pedido pedido = EnsureHasPermissionToPedido(id);
            Representante representante = Repository.GetRepresentante();
            IPrintTemplate printTemplate = m_PrintTemplateSelector.GetPrintTemplate(representante, pedido);
            string vendedorPrint = GetVendedorPrint(representante, pedido);
            PedidoPrintViewModel pedidoPrintViewModel = new PedidoPrintViewModel(representante.RepresentanteInfo, pedido, printTemplate.GetNumero(pedido), vendedorPrint);
            return View(printTemplate.ViewName, pedidoPrintViewModel);
        }

        internal static string GetVendedorPrint(Representante representante, Pedido pedido)
        {
            if (representante.RepresentanteInfo.VendedorPedidoAttribute != null)
            {
                AttributeValue attributeValue =
                    pedido.Vendedor.AttributeValues.FirstOrDefault(
                        x => x.Attribute == representante.RepresentanteInfo.VendedorPedidoAttribute);
                if (attributeValue != null)
                {
                    return attributeValue.Value;
                }
            }
            return pedido.VendedorNome;
        }
    }
}
